#include "server.h"

int sendMessageToClient(int fd, char *buf, int sendLength) {
    train_t train;
    memset(&train, 0, sizeof(train));
    train.length = sendLength;
    memcpy(train.data, buf, sendLength);
    ssize_t sendRet = send(fd, &train, sizeof(train.length) + sendLength, 0);
    ERROR_CHECK(sendRet, -1, "send");
    return 0;
}

ssize_t recvStdin(char *buf, int bufLength) {
    memset(buf, 0, bufLength);
    ssize_t rdRet = read(STDIN_FILENO, buf, bufLength);
    ERROR_CHECK(rdRet, -1, "read");
    return rdRet;
}

ssize_t recvMessageFromClient(int fd, char *buf, int bufLength) {
    train_t train;
    memset(buf, 0, bufLength);
    memset(&train, 0, sizeof(train));
    ssize_t recvRet = recv(fd, &train.length, sizeof(train.length), 0);
    ERROR_CHECK(recvRet, -1, "recv");
    recvRet = recv(fd, train.data, train.length, 0);
    ERROR_CHECK(recvRet, -1, "recv");
    memcpy(buf, train.data, train.length);
    return recvRet;
}

int recvn(int sockfd, void *buf, int length){
    int total = 0; //已经收到的总长度
    char *p = (char *)buf;
    while(total < length){
        ssize_t sret = recv(sockfd,p+total,length-total,0);
        total += sret;
    }
    return 0;
}


int recvFileFromClient(int fd, MYSQL *mysql, threadPool_t *pThreadPool, int pid, char *virtualPath) {
    
    /*文件名*/
    train_t train;
    recvn(fd,&train.length,sizeof(train.length));
    recvn(fd,train.data,train.length);
    char filepath[4096]={0};
    char filename[4096]={0};
    char tmp[1024] = {0};
    memcpy(filepath,train.data,train.length);
    cutTail(filepath, tmp, filename);

    /*文件哈希值*/
    recvn(fd,&train.length,sizeof(train.length));
    recvn(fd,train.data,train.length);
    char md5[128];
    memcpy(md5,train.data,train.length);
    printf("md5=%s\n",md5);
    /*文件路径*/
    char serverPath[512];
    sprintf(serverPath,"%s%s",pThreadPool->home,md5);
    int filefd = open(serverPath,O_RDWR|O_CREAT,0666);
    /*文件长度*/
    off_t filesize;
    recvn(fd,&train.length,sizeof(train.length));
    recvn(fd,train.data,train.length);
    memcpy(&filesize,train.data,sizeof(filesize));
    printf("filesize = %ld\n", filesize);
    ftruncate(filefd,filesize);
    /*文件*/
    char *p = (char *)mmap(NULL,filesize,PROT_READ|PROT_WRITE,MAP_SHARED,filefd,0);
    recvn(fd,p,filesize);
    /*将文件路径存入数据库*/
    insertFile(filename, virtualPath,filesize,md5,pThreadPool->userBuffer[fd],pid, mysql);

    munmap(p,filesize);
    close(filefd);
    return 0;
}

int sendFileToClient(int fd, char *serverPath, char *clientPath) {
    
    /*文件名*/
    train_t train;
    train.length = strlen(clientPath);
    memcpy(train.data,clientPath,train.length);
    send(fd,&train,sizeof(train.length)+train.length,MSG_NOSIGNAL);
    /**文件哈希值*/
    /*char md5[128];*/
    /*changeToMd5(localPath,md5);*/
    /*train.length=strlen(md5);*/
    /*printf("md5length:%d\n",train.length);*/
    /*memcpy(train.data,md5,train.length);*/
    /*send(fd,&train,sizeof(train.length)+train.length,MSG_NOSIGNAL);*/
    /*接收偏移量*/
    off_t offset;
    recv(fd,&offset,sizeof(offset),0);

    /*文件长度*/
    int filefd = open(serverPath,O_RDWR);
    ERROR_CHECK(filefd,-1,"filefd");
    struct stat statbuf;
    fstat(filefd,&statbuf);
    train.length = sizeof(statbuf.st_size);
    memcpy(train.data,&statbuf.st_size,train.length);
    send(fd,&train,sizeof(train.length)+train.length,MSG_NOSIGNAL);
    // ftruncate(fd,statbuf.st_size);
    // char *p = (char *)mmap(NULL,statbuf.st_size,PROT_READ|PROT_WRITE,MAP_SHARED,fd,0);
     //send(netfd,p,statbuf.st_size,MSG_NOSIGNAL);
    // munmap(p,statbuf.st_size);
    /*文件*/
    sendfile(fd,filefd,&offset,statbuf.st_size - offset);

    close(filefd);
    return 0;
}

